package be.groept.ace.cursusplanning.controller;

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.util.ArrayList;
import java.util.List;

import javax.swing.JList;
import javax.swing.ListSelectionModel;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;

import be.groept.ace.cursusplanning.model.AangebodenCursus;
import be.groept.ace.cursusplanning.model.Cursist;
import be.groept.ace.cursusplanning.model.Inschrijving;
import be.groept.ace.cursusplanning.model.containers.Cursisten;
import be.groept.ace.cursusplanning.model.containers.Cursussen;
import be.groept.ace.cursusplanning.model.containers.Inschrijvingen;
import be.groept.ace.cursusplanning.persistency.IDBMS;
import be.groept.ace.cursusplanning.utils.Datum;
import be.groept.ace.cursusplanning.utils.observer.EventArgs;
import be.groept.ace.cursusplanning.utils.observer.Subscriber;

public class InschrijvingController {
	private Inschrijvingen inschrijvingenModel;
	private Cursisten cursistenModel;
	private Cursussen cursussenModel;
	private IDBMS database;
	
	Cursist geselecteerdeCursist;
	
	public InschrijvingController(Inschrijvingen inschrijvingenModel, Cursisten cursistenModel, Cursussen cursussenModel, IDBMS database) {
		this.inschrijvingenModel = inschrijvingenModel;
		this.cursistenModel = cursistenModel;
		this.cursussenModel = cursussenModel;
		this.database = database;
	}
	
	private ItemListener cursistComboBoxListener = new ItemListener() {
		@Override
		public void itemStateChanged(ItemEvent event) {
			geselecteerdeCursist = (Cursist)event.getItem();
			inschrijvingenModel.fireInschrijvingenVoorCursist(geselecteerdeCursist);
			cursistenModel.fireAangeduideCursistChanged(geselecteerdeCursist);
			cursussenModel.fireAlleAangebodenCursussenNogNietIngeschrevenVoorCursist(geselecteerdeCursist);
		}
	};
	
	public ItemListener getCursistComboBoxListener() {
		return cursistComboBoxListener;
	}
	
	private ListSelectionListener reedsIngeschrevenListListener = new ListSelectionListener() {
		
		@Override
		public void valueChanged(ListSelectionEvent event) {
			JList list = (JList)event.getSource();
			ListSelectionModel lsm = list.getSelectionModel();
			List<Inschrijving> geselecteerdeInschrijvingen = new ArrayList<Inschrijving>();
			if (!lsm.isSelectionEmpty()) {
				int minIndex = lsm.getMinSelectionIndex();
	            int maxIndex = lsm.getMaxSelectionIndex();
	            for (int i = minIndex; i <= maxIndex; i++) {
	                if (lsm.isSelectedIndex(i)) {
	                    geselecteerdeInschrijvingen.add((Inschrijving)list.getModel().getElementAt(i));
	                }
	            }
	            if (geselecteerdeInschrijvingen.size() > 0)
	            	inschrijvingenModel.fireGeselecteerdeInschrijving(geselecteerdeInschrijvingen.toArray(new Inschrijving[geselecteerdeInschrijvingen.size()]));
			} else {
				inschrijvingenModel.fireGeselecteerdeInschrijving(new Inschrijving[0]);
			}
		}
	};
	
	public ListSelectionListener getReedsIngeschrevenListListener() {
		return reedsIngeschrevenListListener;
	}
	
	private Subscriber<AangebodenCursus> schrijfInSubscriber = new Subscriber<AangebodenCursus>() {

		@Override
		public void update(EventArgs<AangebodenCursus> event) {
			AangebodenCursus geselecteerdeAangebodenCursus = event.getSource();
			if(geselecteerdeAangebodenCursus.magDeelnemenAanAangebodenCursus(geselecteerdeCursist)) {
				Inschrijving inschrijving = new Inschrijving(new Datum(), geselecteerdeCursist, geselecteerdeAangebodenCursus);
				inschrijvingenModel.add(inschrijving);
				geselecteerdeCursist.addInschrijving(inschrijving);
				geselecteerdeAangebodenCursus.addInschrijvingen(inschrijving);
				
				database.saveOrSwapInschrijving(inschrijving);
				database.saveOrSwapCursist(geselecteerdeCursist);
				
				cursussenModel.fireAlleAangebodenCursussenNogNietIngeschrevenVoorCursist(geselecteerdeCursist);
				inschrijvingenModel.fireInschrijvingenVoorCursist(geselecteerdeCursist);
			}
		}
		
	};
	
	public Subscriber<AangebodenCursus> getSchrijfInSubscriber() {
		return schrijfInSubscriber;
		
	}
	
	private Subscriber<Inschrijving> schrijfUitSubscriber = new Subscriber<Inschrijving>() {

		@Override
		public void update(EventArgs<Inschrijving> event) {
			Inschrijving inschrijving = event.getSource();
			geselecteerdeCursist.removeInschrijving(inschrijving);
			for(int i = 0; i < inschrijvingenModel.getAll().size(); i++) {
				if(inschrijvingenModel.get(i).equals(inschrijving)) {
					inschrijvingenModel.remove(i);
					break;
				}
			}
			inschrijving.getAangebodenCursus().removeInschrijving(inschrijving);
			
			database.saveOrSwapInschrijving(inschrijving);
			database.saveOrSwapCursist(geselecteerdeCursist);
			
			cursussenModel.fireAlleAangebodenCursussenNogNietIngeschrevenVoorCursist(geselecteerdeCursist);
			inschrijvingenModel.fireInschrijvingenVoorCursist(geselecteerdeCursist);
			
		}
		
	};
	
	public Subscriber<Inschrijving> getSchrijfUitSubscriber() {
		return schrijfUitSubscriber;
	}
}
